﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections.ObjectModel;
using QLTT.Models;
using QLTT.Commands;
using System.Windows.Input;
using System.Windows;

namespace QLTT.ViewModels
{
    class ClassScheduleViewModel : WorkspaceViewModel
    {
        private ClassViewModel _selectedClassViewModel;
        private StudentClassViewModel _studentClassViewModel;
        ObservableCollection<List<List<ScheduleViewModel>>> _lstClassSchedule;
        private icanDataContext _dataContext;
        private DelegateCommand _findCommand;
        private DelegateCommand _chooseClassCommand;
        private IQueryable<ClassViewModel> _query;
        private string _className;
        private bool _isChangingClass = false;
        public ClassScheduleViewModel(icanDataContext dataContext, bool isSelectClass)
        {
            _dataContext = dataContext;
            this.ChooseButtonVisibility = isSelectClass?System.Windows.Visibility.Visible:System.Windows.Visibility.Hidden;
            var query = from c in _dataContext.Classes where c.EndDate >= DateTime.Today select c.ID;
            List<long> lstIDs = query.ToList();
            var query2 = from s in _dataContext.Schedules where lstIDs.Contains(s.Class) select new ScheduleViewModel(s, _dataContext);
            List<ScheduleViewModel> lstSchedules = query2.ToList();
            InitDataForGrid(lstSchedules);

            this.Level = 0;
            this.Room = 0;
            this.Teacher = 0;
            this.Status = Properties.Resources.Combo_AllClass_Status_InProgressOrNotYetStart;
            base.DisplayName = Properties.Resources.Base_DisplayName_ClassSchedule;
        }
        public ClassScheduleViewModel(icanDataContext dataContext, bool isSelectClass,StudentClassViewModel scVM)
        {
            _dataContext = dataContext;
            _studentClassViewModel = scVM;
            _isChangingClass = true;
            this.ChooseButtonVisibility = isSelectClass ? System.Windows.Visibility.Visible : System.Windows.Visibility.Hidden;
            var query = from c in _dataContext.Classes where ((c.EndDate >= DateTime.Today)  && (c.ID!=scVM.ID )) select c.ID;
            List<long> lstIDs = query.ToList();
            var query2 = from s in _dataContext.Schedules where lstIDs.Contains(s.Class) select new ScheduleViewModel(s, _dataContext);
            List<ScheduleViewModel> lstSchedules = query2.ToList();
            InitDataForGrid(lstSchedules);

            this.Level = 0;
            this.Room = 0;
            this.Teacher = 0;
            this.Status = Properties.Resources.Combo_AllClass_Status_InProgressOrNotYetStart;
            base.DisplayName = Properties.Resources.Base_DisplayName_ClassSchedule;
        }
        public string Name
        {
            get { return _className; }
            set { _className = value; }
        }
        public long Level { get; set; }
        public long Room { get; set; }
        public long Teacher { get; set; }
        public string Status { get; set; }
        public long ClassTime { get; set; }
        public DateTime StartDate { get; set; }
        public System.Windows.Visibility ChooseButtonVisibility { get; set; }
        public List<LevelViewModel> Levels
        {
            get
            {
                List<LevelViewModel> lstLevel = _dataContext.Levels.Select(lv => new LevelViewModel(_dataContext, lv)).ToList();
                LevelViewModel lvm = new LevelViewModel(_dataContext);
                lvm.Name = QLTT.Properties.Resources.Combo_AllClass_Level_Default;
                lstLevel.Insert(0, lvm);
                return lstLevel;
                //return new List<LevelViewModel>(lstLevel);
            }
        }
        public List<TeacherViewModel> Teachers
        {
            get
            {
                List<TeacherViewModel> lstTeacher = _dataContext.Teachers.Select(t => new TeacherViewModel(_dataContext, t)).ToList();
                TeacherViewModel tm = new TeacherViewModel(_dataContext);
                tm.Name = QLTT.Properties.Resources.Combo_AllClass_Teacher_Default;
                lstTeacher.Insert(0, tm);
                return lstTeacher;
            }
        }
        public List<RoomViewModel> Rooms
        {
            get
            {
                List<RoomViewModel> lstRoom = _dataContext.Rooms.Select(r => new RoomViewModel(_dataContext, r)).ToList();
                RoomViewModel rVM = new RoomViewModel(_dataContext);
                rVM.Name = QLTT.Properties.Resources.Combo_AllClass_Room_Default;
                lstRoom.Insert(0, rVM);
                return lstRoom;
            }
        }
        public List<ClassTimeViewModel> ClassTimes
        {
            get
            {
                List<ClassTimeViewModel> lstClassTime = _dataContext.ClassTimes.Select(ct => new ClassTimeViewModel(_dataContext, ct)).ToList();
                ClassTimeViewModel rVM = new ClassTimeViewModel(_dataContext);
                lstClassTime.Insert(0, rVM);
                return lstClassTime;
            }
        }
        public string[] Statuses
        {
            get
            {
                return new string[]
                {
                    Properties.Resources.Combo_AllClass_Status_InProgressOrNotYetStart,
                    Properties.Resources.Combo_AllClass_Stutus_InProgress,
                    Properties.Resources.Combo_AllClass_Status_NotYetStart,
                    Properties.Resources.Combo_AllClass_Status_Finished,
                    Properties.Resources.Combo_AllClass_Status_InProgressOrFinished,
                    Properties.Resources.Combo_AllClass_Status_Default
                    
                };
            }
        }
        public ObservableCollection<List<List<ScheduleViewModel>>> ClassSchedules
        {
            get { return _lstClassSchedule; }
            set
            {
                _lstClassSchedule= value;
                base.OnPropertyChanged("ClassSchedules");
            }
        }
        public ICommand FindCommand
        {
            get
            {
                if (_findCommand == null)
                {
                    _findCommand = new DelegateCommand(Find);
                }
                return _findCommand;
            }
        }
        public ICommand ChooseClassCommand
        {
            get
            {
                if (_chooseClassCommand == null)
                {
                    _chooseClassCommand = new DelegateCommand(ChooseClass);
                }
                return _chooseClassCommand;
            }
        }
        private void InitDataForGrid(List<ScheduleViewModel> lstScheduleViewModels)
        {
            ObservableCollection<List<List<ScheduleViewModel>>> classSchedules = new ObservableCollection<List<List<ScheduleViewModel>>>();
            //get classtime
            List<long> lstClassTimeIDs = _dataContext.Schedules.Select(s => s.ClassTime).Distinct().ToList();
            foreach (long id in lstClassTimeIDs)
            {
                List<List<ScheduleViewModel>> lstSVMs = new List<List<ScheduleViewModel>>();
                for (int i = 0; i < 8; i++)
                    lstSVMs.Add(new List<ScheduleViewModel>());
                Schedule schedule = new Schedule();
                schedule.ClassTime = id;
                lstSVMs[7].Add(new ScheduleViewModel(schedule, _dataContext));
                classSchedules.Add(lstSVMs);
            }
           
            foreach (ScheduleViewModel sVM in lstScheduleViewModels)
            {
                classSchedules[lstClassTimeIDs.IndexOf(sVM.ClassTime.ID)][sVM.DayOfWeek].Add(sVM);
            }
            this.ClassSchedules = classSchedules;
        }

        public void Find()
        {
            IQueryable<Class> myQuery = _dataContext.Classes;
            
            //Add more Where Conditions here
            if (this.Level > 0)
                myQuery = myQuery.Where<Class>(oClass => oClass.Level == this.Level);
            if (this.Teacher > 0)
            {
                var query = from s in _dataContext.Schedules where s.Teacher == this.Teacher select s.Class;
                List<long> lstIDs = query.ToList();
                myQuery = myQuery.Where<Class>(oClass => lstIDs.Contains(oClass.ID));
            }
            if (this.Room > 0)
                myQuery = myQuery.Where<Class>(oClass => oClass.Room == this.Room);
            
            if (this.Status != Properties.Resources.Combo_AllClass_Status_Default)
            {
                if (this.Status == Properties.Resources.Combo_AllClass_Status_InProgressOrNotYetStart)
                {
                    myQuery = myQuery.Where(oClass => oClass.EndDate >= DateTime.Today);
                }
                else if (this.Status == Properties.Resources.Combo_AllClass_Stutus_InProgress)
                {
                    myQuery = myQuery.Where(oClass => oClass.EndDate >= DateTime.Today && oClass.StartDate <= DateTime.Today);
                }
                else if (this.Status == Properties.Resources.Combo_AllClass_Status_NotYetStart)
                {
                    myQuery = myQuery.Where(oClass => oClass.StartDate > DateTime.Today);
                }
                else if (this.Status == Properties.Resources.Combo_AllClass_Status_InProgressOrFinished)
                {
                    myQuery = myQuery.Where(oClass => oClass.StartDate < DateTime.Today);
                }
                else if (this.Status == Properties.Resources.Combo_AllClass_Status_Finished)
                {
                    myQuery = myQuery.Where(oClass => oClass.EndDate < DateTime.Today);
                }
            }
            //Select
            List<long> lstClassIDs = myQuery.Select(oClass => oClass.ID).ToList();
            var query2 = from s in _dataContext.Schedules where lstClassIDs.Contains(s.Class) select new ScheduleViewModel(s, _dataContext);
            List<ScheduleViewModel> lstSchedules = query2.ToList();
            if (this.Teacher > 0)
            {
                lstSchedules = lstSchedules.Where(s => s.Teacher == this.Teacher).ToList();
            }
            InitDataForGrid(lstSchedules);
        }
        private void ChooseClass()
        {
            if (_selectedClassViewModel != null)
            {
                if (_isChangingClass)
                {
                    try
                    {
                        _studentClassViewModel.Class = _selectedClassViewModel.ID;
                        _dataContext.SubmitChanges();
                    }
                    catch (Exception ex)
                    {
                        System.Diagnostics.EventLog.WriteEntry("Application", ex.ToString(), System.Diagnostics.EventLogEntryType.Error);
                    }
                }
                else
                    Mediator.NotifyColleagues<ClassViewModel>(Messages.UpdateChoosingClass, _selectedClassViewModel);
                Mediator.NotifyColleagues<WorkspaceViewModel>(Messages.WorkspaceRemove, this);
            }
        }
        
        private bool IsItemSelected()
        {
            return true;
        }
        
      

        [MediatorLib.MediatorMessageSink(Messages.ClassSelectedChanged, ParameterType = typeof(ClassViewModel))]
        public void UpdateClassSelection(ClassViewModel cVM)
        {
            //foreach (List<List<ScheduleViewModel>> lstlstSVM in this.ClassSchedules)
            //{
            //    foreach (List<ScheduleViewModel> lstSVM in lstlstSVM)
            //    {
            //        foreach (ScheduleViewModel sVM in lstSVM)
            //        {
            //            if (sVM.Class.ID != cVM.ID)
            //                sVM.Class.IsSelected = false;
            //        }
            //    }
            //}
            _selectedClassViewModel = cVM;
        }
    }
}

